# load required libraries
library(tidyverse)
── Attaching packages ─────────────────────────────────────── tidyverse 1.2.1 ──
✔ ggplot2 3.0.0     ✔ purrr   0.2.5
✔ tibble  1.4.2     ✔ dplyr   0.7.6
✔ tidyr   0.8.1     ✔ stringr 1.3.1
✔ readr   1.1.1     ✔ forcats 0.3.0
── Conflicts ────────────────────────────────────────── tidyverse_conflicts() ──
✖ dplyr::filter() masks stats::filter()
✖ dplyr::lag()    masks stats::lag()
library(langcog) # source: https://github.com/langcog/langcog-package

Attaching package: ‘langcog’

The following object is masked from ‘package:base’:

    scale
library(psych)

Attaching package: ‘psych’

The following objects are masked from ‘package:ggplot2’:

    %+%, alpha
library(lme4)
Loading required package: Matrix

Attaching package: ‘Matrix’

The following object is masked from ‘package:tidyr’:

    expand
library(cowplot)

Attaching package: ‘cowplot’

The following object is masked from ‘package:ggplot2’:

    ggsave
# set theme for ggplots
theme_set(theme_bw())

Data preparation

d_all <- # d_us_ad_pilot %>% rownames_to_column("subid") %>%
  d_gh_ad %>% rownames_to_column("subid") %>%
  full_join(d_gh_ch %>% rownames_to_column("subid")) %>%
  full_join(d_th_ad %>% rownames_to_column("subid")) %>%
  full_join(d_th_ch %>% rownames_to_column("subid")) %>%
  full_join(d_vt_ad %>% rownames_to_column("subid")) %>%
  full_join(d_vt_ch %>% rownames_to_column("subid")) %>%
  column_to_rownames("subid")
Joining, by = c("subid", "choose what to do", "feel guilty", "feel happy", "feel love", "feel pain", "feel proud", "feel sad", "feel scared", "feel shy", "feel sick, like when you feel like you might vomit", "feel tired", "figure out how to do things", "get angry", "get hungry", "get hurt feelings", "hear things", "pray", "remember things", "sense temperatures", "sense when things are far away", "smell things", "think about things")
Joining, by = c("subid", "choose what to do", "feel guilty", "feel happy", "feel love", "feel pain", "feel proud", "feel sad", "feel scared", "feel shy", "feel sick, like when you feel like you might vomit", "feel tired", "figure out how to do things", "get angry", "get hungry", "get hurt feelings", "hear things", "pray", "remember things", "sense temperatures", "sense when things are far away", "smell things", "think about things")
Joining, by = c("subid", "choose what to do", "feel guilty", "feel happy", "feel love", "feel pain", "feel proud", "feel sad", "feel scared", "feel shy", "feel sick, like when you feel like you might vomit", "feel tired", "figure out how to do things", "get angry", "get hungry", "get hurt feelings", "hear things", "pray", "remember things", "sense temperatures", "sense when things are far away", "smell things", "think about things")
Joining, by = c("subid", "choose what to do", "feel guilty", "feel happy", "feel love", "feel pain", "feel proud", "feel sad", "feel scared", "feel shy", "feel sick, like when you feel like you might vomit", "feel tired", "figure out how to do things", "get angry", "get hungry", "get hurt feelings", "hear things", "pray", "remember things", "sense temperatures", "sense when things are far away", "smell things", "think about things")
Joining, by = c("subid", "choose what to do", "feel guilty", "feel happy", "feel love", "feel pain", "feel proud", "feel sad", "feel scared", "feel shy", "feel sick, like when you feel like you might vomit", "feel tired", "figure out how to do things", "get angry", "get hungry", "get hurt feelings", "hear things", "pray", "remember things", "sense temperatures", "sense when things are far away", "smell things", "think about things")

Shared conceptual structure

Pooling all participants from all sites together into a common factor structure.

Parallel analysis

How many factors to retain?

reten_all_PA <- fa.parallel(d_all, plot = F); reten_all_PA
Parallel analysis suggests that the number of factors =  4  and the number of components =  2 
Call: fa.parallel(x = d_all, plot = F)
Parallel analysis suggests that the number of factors =  4  and the number of components =  2 

 Eigen Values of 
reten_all_par <- reten_all_PA$nfact

What are these factors?

efa_all_par <- fa(d_all, nfactors = reten_all_par, rotate = "oblimin",
                  scores = "tenBerge", impute = "median")
Loading required namespace: GPArotation
heatmap_fun(efa_all_par, factor_names = c("COGNITIVE", "BODILY", "SOCIAL-EMOTIONAL", "[other]")) + 
  labs(title = "Factor loadings (data pooled across all samples)")
the condition has length > 1 and only the first element will be usedJoining, by = "capacity"
Joining, by = "factor"

Which capacities are attributed to which targets?

Factor scores

scoresplot_fun(efa_all_par, target = "all",
               factor_names = c("COGNITIVE", "BODILY", 
                                "SOCIAL-EMOTIONAL", "[other]")) + 
  labs(title = "Factor scores (by sample, factor, and target entity)",
       subtitle = "All targets")
the condition has length > 1 and only the first element will be usedIgnoring unknown aesthetics: y

scoresplot_fun(efa_all_par, target = c("ghosts", "God", "children"),
               factor_names = c("COGNITIVE", "BODILY",
                                "SOC.-EMO.", "[other]")) + 
  labs(title = "Factor scores (by sample, factor, and target entity)",
       subtitle = "Human and 'supernatural' targets only")
the condition has length > 1 and only the first element will be usedthe condition has length > 1 and only the first element will be usedthe condition has length > 1 and only the first element will be usedthe condition has length > 1 and only the first element will be usedIgnoring unknown aesthetics: y

itemsplot_fun(efa_all_par, target = c("ghosts", "God", "children")) +
  labs(title = "Parallel Analysis")
the condition has length > 1 and only the first element will be usedthe condition has length > 1 and only the first element will be usedthe condition has length > 1 and only the first element will be usedJoining, by = "capacity"

|=============================                          | 53% ~2 s remaining     
|==============================                         | 55% ~2 s remaining     
|===============================                        | 57% ~2 s remaining     
|================================                       | 59% ~2 s remaining     
|=================================                      | 60% ~1 s remaining     
|==================================                     | 62% ~1 s remaining     
|==================================                     | 63% ~1 s remaining     
|====================================                   | 66% ~1 s remaining     
|=====================================                  | 67% ~1 s remaining     
|=====================================                  | 69% ~1 s remaining     
|=======================================                | 71% ~1 s remaining     
|=======================================                | 72% ~1 s remaining     
|========================================               | 74% ~1 s remaining     
|=========================================              | 76% ~1 s remaining     
|==========================================             | 77% ~1 s remaining     
|===========================================            | 79% ~1 s remaining     
|===========================================            | 80% ~1 s remaining     
|============================================           | 81% ~1 s remaining     
|=============================================          | 83% ~1 s remaining     
|==============================================         | 85% ~1 s remaining     
|===============================================        | 87% ~0 s remaining     
|================================================       | 89% ~0 s remaining     
|=================================================      | 91% ~0 s remaining     
|===================================================    | 93% ~0 s remaining     
|====================================================   | 95% ~0 s remaining     
|=====================================================  | 97% ~0 s remaining     
|====================================================== | 99% ~0 s remaining     
Joining, by = c("factor", "capacity", "order")

Summary scores

factors_par <- efa_all_par$loadings[] %>%
  data.frame() %>%
  rownames_to_column("capacity") %>%
  gather(factor, loading, -capacity) %>%
  group_by(capacity) %>%
  top_n(1, loading) %>%
  ungroup() %>%
  arrange(factor, desc(loading)) %>%
  mutate(order = 1:nrow(.))
factors_par_howmany <- factors_par %>%
  count(factor)
factors_par_culled <- factors_par %>%
  group_by(factor) %>%
  top_n(min(factors_par_howmany$n), loading) %>%
  ungroup() %>%
  arrange(factor, desc(loading)) %>%
  mutate(order = 1:nrow(.))
scores_par_prelim <- d_all %>%
  rownames_to_column("site_age_subid_target_entity") %>%
  gather(capacity, response, -site_age_subid_target_entity) %>%
  mutate(site = gsub("_.*$", "", site_age_subid_target_entity),
         age = gsub("_.*$", "", gsub("^.._", "", site_age_subid_target_entity)),
         subid = gsub("_target.*$", "", site_age_subid_target_entity),
         target = gsub("^.*target_", "", site_age_subid_target_entity)) %>%
  mutate(target = case_when(target == "pigs" ~ NA_character_,
                            target == "NA" ~ NA_character_,
                            target == "crickets" ~ "beetles",
                            TRUE ~ target)) %>%
  mutate(site = factor(site, levels = c("us", "gh", "th", "ch", "vt"),
                       labels = c("US", "Ghana", "Thailand", "China", "Vanuatu")),
         age = factor(age, levels = c("ad", "ch"),
                      labels = c("adults", "children")),
         target = factor(target,
                         levels = c("rocks", "flowers", "cell phones", 
                                    "beetles", "chickens", "mice", 
                                    "dogs", "children", 
                                    "ghosts", "God"))) %>%
  select(-site_age_subid_target_entity) %>%
  full_join(factors_par_culled) %>%
  # full_join(factors_par) %>%
  mutate(factor = factor(factor, levels = c("MR2", "MR1", "MR3", "MR4"),
                         labels = c("BODILY", "COGNITIVE", 
                                    "SOCIAL-EMOTIONAL", "[other]"))) %>%
  filter(!is.na(target), !is.na(factor)) %>%
  distinct()
Joining, by = "capacity"
scores_par <- scores_par_prelim %>%
  group_by(site, age, subid, target, factor) %>%
  summarise(score = mean(response, na.rm = T)) %>%
  ungroup()
scores_par_mb <- scores_par %>% 
  group_by(site, age, target, factor) %>%
  multi_boot_standard(col = "score", na.rm = T) %>%
  ungroup()
# calculate reliability
scores_par_prelim_wide <- scores_par_prelim %>%
  full_join(factors_par_culled) %>%
  filter(!is.na(factor), !is.na(subid)) %>% 
  arrange(factor, desc(loading)) %>%
  select(subid, capacity, response) %>%
  spread(capacity, response) %>%
  select(subid, factors_par_culled$capacity) %>%
  column_to_rownames("subid")
Joining, by = c("capacity", "factor", "loading", "order")
Column `factor` joining factor and character vector, coercing into character vector
# BODILY
alpha(scores_par_prelim_wide[5:8])$total
# "COGNITIVE"
alpha(scores_par_prelim_wide[1:4])$total
# "SOCIAL-EMOTIONAL"
alpha(scores_par_prelim_wide[9:12])$total
ggplot(scores_par, aes(x = target, y = score, color = factor)) +
  facet_grid(cols = vars(site, age), rows = vars(factor)) +
  geom_jitter(height = 0.02, width = 0.2, alpha = 0.2, show.legend = F) +
  geom_pointrange(data = scores_par_mb,
                  aes(y = mean, ymin = ci_lower, ymax = ci_upper),
                  fatten = 2, color = "black") +
  scale_color_brewer(palette = "Set1") +
  theme(axis.text.x = element_text(angle = 45, hjust = 1, vjust = 1))

ggplot(scores_par %>% filter(target %in% c("children", "ghosts", "God")), 
       aes(x = target, y = score, color = factor)) +
  facet_grid(cols = vars(site, age), rows = vars(factor)) +
  geom_jitter(height = 0.02, width = 0.2, alpha = 0.25, show.legend = F) +
  geom_pointrange(data = scores_par_mb %>%
                    filter(target %in% c("children", "ghosts", "God")),
                  aes(y = mean, ymin = ci_lower, ymax = ci_upper),
                  fatten = 2, color = "black") +
  scale_color_brewer(palette = "Set1") +
  theme(axis.text.x = element_text(angle = 45, hjust = 1, vjust = 1))

Minimizing BIC

How many factors to retain?

reten_all_BIC <- VSS(d_all, plot = F); reten_all_BIC
reten_all_bic <- data.frame(reten_all_BIC$vss.stats %>% rownames_to_column("nfact") %>% top_n(-1, BIC))$nfact %>% as.numeric()

What are these factors?

efa_all_bic <- fa(d_all, nfactors = reten_all_bic, rotate = "oblimin",
                  scores = "tenBerge", impute = "median")
heatmap_fun(efa_all_bic, 
            factor_names = c("COGNITIVE", "BODILY", "SOCIAL-EMOTIONAL", "other")) + 
  # labs(title = "Minimizing BIC")
  labs(x = "Figure 1: Shared conceptual structure") +
  theme(axis.title.x = element_text(hjust = 0)) +
  guides(fill = guide_colorbar("factor loading", barheight = 15))

Which capacities are attributed to which targets?

scoresplot_fun(efa_all_bic, target = "all", highlight = "supernatural",
            factor_names = c("COGNITIVE", "BODILY", "SOCIAL-EMOTIONAL", "other")) + 
  theme(axis.text.x = element_text(angle = 90, hjust = 1, vjust = 1,
                                   color = c(rep("black", 8),
                                             rep("#984ea3", 2)),
                                   face = c(rep("plain", 8),
                                            rep("bold", 2)))) +
  scale_fill_manual(values = c("#e41a1c", "#4daf4a", "#377eb8", "gray")) +
  # labs(title = "Minimizing BIC")
  labs(title = "Figure 2: Factor scores")
scoresplot_fun(efa_all_bic, target = c("ghosts", "God", "children")) + 
  # scale_fill_manual(values = c("#e41a1c", "#4daf4a", "#377eb8")) +
  labs(title = "Minimizing BIC")
itemsplot_fun(efa_all_bic, target = c("ghosts", "God", "children")) + 
  labs(title = "Minimizing BIC")

Preset criteria

How many factors to retain?

reten_all_k <- reten_fun(d_all, rot_type = "oblimin"); reten_all_k

What are these factors?

efa_all_k <- fa(d_all, nfactors = reten_all_k, rotate = "oblimin",
                  scores = "tenBerge", impute = "median")
heatmap_fun(efa_all_k) + 
  labs(title = "Preset criteria (Weisman et al., 2017)")

Which capacities are attributed to which targets?

scoresplot_fun(efa_all_k, target = "all") + 
  labs(title = "Preset criteria (Weisman et al., 2017)")
scoresplot_fun(efa_all_k, target = c("ghosts", "God", "children")) + 
  labs(title = "Preset criteria (Weisman et al., 2017)")
itemsplot_fun(efa_all_k, target = c("ghosts", "God", "children")) + 
  labs(title = "Preset criteria (Weisman et al., 2017)")

3 factors

What are these factors?

efa_all_3 <- fa(d_all, nfactors = 3, rotate = "oblimin",
                scores = "tenBerge", impute = "median")
heatmap_fun(efa_all_3, 
            factor_names = c("COGNITIVE", "BODILY", "SOCIAL-EMOTIONAL")) + 
  labs(x = "Shared concpetual structure") +
  theme(axis.title.x = element_text(hjust = 0))
  # labs(title = "Preset criteria (Weisman et al., 2017)")

Which capacities are attributed to which targets?

scoresplot_fun(efa_all_3, target = "all", highlight = "supernatural",
               factor_names = c("COGNITIVE", "BODILY", "SOCIAL-EMOTIONAL")) +
  scale_fill_manual(values = c("#e41a1c", "#4daf4a", "#377eb8")) +
  theme(axis.text.x = element_text(angle = 90, hjust = 1, vjust = 1,
                                   color = c(rep("black", 8),
                                             rep("#984ea3", 2)),
                                   face = c(rep("plain", 8),
                                            rep("bold", 2))))
scoresplot_fun(efa_all_3, target = c("ghosts", "God", "children")) + 
  labs(title = "Preset criteria (Weisman et al., 2017)")
itemsplot_fun(efa_all_3, target = c("ghosts", "God", "children")) + 
  labs(title = "Preset criteria (Weisman et al., 2017)")

Comparing conceptual structures

We’ll extract 4 factors from all samples, to keep things simple.

efa_us_ad_4 <- fa(d_us_ad_pilot, nfactors = 4, rotate = "oblimin")
efa_gh_ad_4 <- fa(d_gh_ad, nfactors = 4, rotate = "oblimin")
efa_gh_ch_4 <- fa(d_gh_ch, nfactors = 4, rotate = "oblimin")
efa_th_ad_4 <- fa(d_th_ad, nfactors = 4, rotate = "oblimin")
efa_th_ch_4 <- fa(d_th_ch, nfactors = 4, rotate = "oblimin")
efa_vt_ad_4 <- fa(d_vt_ad, nfactors = 4, rotate = "oblimin")
efa_vt_ch_4 <- fa(d_vt_ch, nfactors = 4, rotate = "oblimin")
plot_us_ad_4 <- heatmap_fun(efa_us_ad_4) + 
  guides(fill = "none") + 
  labs(x = "US: adults") +
  theme(axis.title.x = element_text(hjust = 0))

plot_gh_ad_4 <- heatmap_fun(efa_gh_ad_4) + 
  guides(fill = "none") + 
  labs(x = "Ghana: adults") +
  theme(axis.title.x = element_text(hjust = 0))

plot_gh_ch_4 <- heatmap_fun(efa_gh_ch_4) + 
  guides(fill = "none") + 
  labs(x = "Ghana: children") +
  theme(axis.title.x = element_text(hjust = 0))

plot_th_ad_4 <- heatmap_fun(efa_th_ad_4) + 
  guides(fill = "none") + 
  labs(x = "Thailand: adults") +
  theme(axis.title.x = element_text(hjust = 0))

plot_th_ch_4 <- heatmap_fun(efa_th_ch_4) + 
  guides(fill = "none") + 
  labs(x = "Thailand: children") +
  theme(axis.title.x = element_text(hjust = 0))

plot_vt_ad_4 <- heatmap_fun(efa_vt_ad_4) + 
  guides(fill = "none") + 
  labs(x = "Vanuatu: adults") +
  theme(axis.title.x = element_text(hjust = 0))

plot_vt_ch_4 <- heatmap_fun(efa_vt_ch_4) + 
  guides(fill = "none") + 
  labs(x = "Vanuatu: children") +
  theme(axis.title.x = element_text(hjust = 0))
plot_grid(#plot_us_ad_4, 
          plot_gh_ad_4, plot_gh_ch_4, plot_th_ad_4, 
          plot_th_ch_4, plot_vt_ad_4, plot_vt_ch_4, 
          ncol = 2, labels = c("A", "B", "C", "D", "E", "F", "G"))

Counts

paste("US adults:", nrow(d_us_ad_pilot))
paste("GH adults:", nrow(d_gh_ad))
paste("GH children:", nrow(d_gh_ch))
paste("TH adults:", nrow(d_th_ad))
paste("TH children:", nrow(d_th_ch))
paste("VT adults:", nrow(d_vt_ad))
paste("VT children:", nrow(d_vt_ch))

paste("Non-US:", sum(nrow(d_gh_ad), nrow(d_gh_ch),
                     nrow(d_th_ad), nrow(d_th_ch),
                     nrow(d_vt_ad), nrow(d_vt_ch)))
LS0tCnRpdGxlOiAiU1JDRCAyMDE5IFN5bXBvc2l1bTogUmVsaWdpb3VzICYgbWV0YXBoeXNpY2FsIGNvbmNlcHRzIChTcmluaXZhc2FuKSIKb3V0cHV0OiAKICBodG1sX25vdGVib29rOgogICAgdG9jOiB0cnVlCiAgICB0b2NfZmxvYXQ6IHRydWUKLS0tCgpgYGB7ciBnbG9iYWxfb3B0aW9ucywgaW5jbHVkZSA9IEZ9CmtuaXRyOjpvcHRzX2NodW5rJHNldChmaWcud2lkdGggPSAzLCBmaWcuYXNwID0gMC42NykKYGBgCgpgYGB7cn0KIyBsb2FkIHJlcXVpcmVkIGxpYnJhcmllcwpsaWJyYXJ5KHRpZHl2ZXJzZSkKbGlicmFyeShsYW5nY29nKSAjIHNvdXJjZTogaHR0cHM6Ly9naXRodWIuY29tL2xhbmdjb2cvbGFuZ2NvZy1wYWNrYWdlCmxpYnJhcnkocHN5Y2gpCmxpYnJhcnkobG1lNCkKbGlicmFyeShjb3dwbG90KQoKIyBzZXQgdGhlbWUgZm9yIGdncGxvdHMKdGhlbWVfc2V0KHRoZW1lX2J3KCkpCmBgYAoKYGBge3IsIGluY2x1ZGUgPSBGfQpzb3VyY2UoIi4vc2NyaXB0cy9tYXhfZmFjdG9yc19lZmEuUiIpCnNvdXJjZSgiLi9zY3JpcHRzL3Bsb3RfZnVuX2JlZXRsZXMuUiIpCnNvdXJjZSgiLi9zY3JpcHRzL3JldGVuX2Z1bi5SIikKc291cmNlKCIuL3NjcmlwdHMvY2xlYW5fZnVuLlIiKQpgYGAKCiMgRGF0YSBwcmVwYXJhdGlvbgoKYGBge3IsIGluY2x1ZGUgPSBGfQpxdWVzdGlvbl9rZXkgPC0gcmVhZC5jc3YoIi9Vc2Vycy9rd2Vpc21hbi9Eb2N1bWVudHMvUmVzZWFyY2ggKFN0YW5mb3JkKS9Qcm9qZWN0cy9UZW1wbGV0b24gR3JhbnQvREVWRUxPUE1FTlRBTCBUQVNLUy9iZWV0bGVzOmRpbWtpZDpmYWN0b3JzL2Rlc2lnbi9iZWV0bGVzIGNiLmNzdiIpCmBgYAoKYGBge3IsIGluY2x1ZGUgPSBGLCB3YXJuaW5nID0gRkFMU0V9CiMgVVMgYWR1bHRzIFBJTE9UCmRfdXNfYWRfcGlsb3RfcmF3IDwtIHJlYWQuY3N2KCIvVXNlcnMva3dlaXNtYW4vRG9jdW1lbnRzL1Jlc2VhcmNoIChTdGFuZm9yZCkvUHJvamVjdHMvVGVtcGxldG9uIEdyYW50L0RFVkVMT1BNRU5UQUwgVEFTS1MvYmVldGxlczpkaW1raWQ6ZmFjdG9ycy9hbmFseXNpcy9fVVMgcGlsb3QvYmVldGxlc19waWxvdDJfdGlkeS5jc3YiKQpkX3VzX2FkX3BpbG90IDwtIGRfdXNfYWRfcGlsb3RfcmF3ICU+JQogIGZpbHRlcihzY2FsZSA9PSAiYmVldGxlcyIpICU+JQogIGRpc3RpbmN0KHN1YmlkLCBjaGFyYWN0ZXIsIHF1ZXN0aW9uLCByZXNwb25zZSkgJT4lCiAgZmlsdGVyKCFxdWVzdGlvbiAlaW4lIGMoImJsZWVkIiwgIm1pbmQiLCAic291bCIpKSAlPiUKICBtdXRhdGUocXVlc3Rpb24gPSByZWNvZGUocXVlc3Rpb24sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICJhZGRfc3VidHJhY3QiID0gImFkZCBhbmQgc3VidHJhY3QgbnVtYmVycyIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICJhbmdyeSIgPSAiZ2V0IGFuZ3J5IiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIyAiYmxlZWQiID0gImJsZWVkIHdoZW4gdGhleSB0b3VjaCBzb21ldGhpbmcgc2hhcnAiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAiY2hvb3NlIiA9ICJjaG9vc2Ugd2hhdCB0byBkbyIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICJmaWd1cmVfb3V0IiA9ICJmaWd1cmUgb3V0IGhvdyB0byBkbyB0aGluZ3MiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAiZ3VpbHR5IiA9ICJmZWVsIGd1aWx0eSIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICJoYXBweSIgPSAiZmVlbCBoYXBweSIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICJoZWFyIiA9ICJoZWFyIHRoaW5ncyIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICJodW5ncnkiID0gImdldCBodW5ncnkiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAiaHVydF9mZWVsaW5ncyIgPSAiZ2V0IGh1cnQgZmVlbGluZ3MiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAibG92ZSIgPSAiZmVlbCBsb3ZlIiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIyAibWluZCIgPSAiaGF2ZSBtaW5kcyIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICJwYWluIiA9ICJmZWVsIHBhaW4iLAogICAgICAgICAgICAgICAgICAgICAgICAgICAicHJheSIgPSAicHJheSIsIAogICAgICAgICAgICAgICAgICAgICAgICAgICAicHJvdWQiID0gImZlZWwgcHJvdWQiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAicmVtZW1iZXIiID0gInJlbWVtYmVyIHRoaW5ncyIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICJzYWQiID0gImZlZWwgc2FkIiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgInNjYXJlZCIgPSAiZmVlbCBzY2FyZWQiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAic2Vuc2VfZmFyIiA9ICJzZW5zZSB3aGVuIHRoaW5ncyBhcmUgZmFyIGF3YXkiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAic2Vuc2VfdGVtcCIgPSAic2Vuc2UgdGVtcGVyYXR1cmVzIiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgInNoeSIgPSAiZmVlbCBzaHkiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAic2ljayIgPSAiZmVlbCBzaWNrLCBsaWtlIHdoZW4geW91IGZlZWwgbGlrZSB5b3UgbWlnaHQgdm9taXQiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAic21lbGwiID0gInNtZWxsIHRoaW5ncyIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICMgInNvdWwiID0gImhhdmUgc291bHMiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAidGhpbmsiID0gInRoaW5rIGFib3V0IHRoaW5ncyIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICJ0aXJlZCIgPSAiZmVlbCB0aXJlZCIpKSAlPiUKICBzcHJlYWQocXVlc3Rpb24sIHJlc3BvbnNlKSAlPiUKICBzZWxlY3QoLXN1YmlkKSAlPiUKICBtdXRhdGUoc3ViaWQgPSBwYXN0ZSgidXNfYWQiLAogICAgICAgICAgICAgICAgICAgICAgIDEwMDAxOigxMDAwMCtsZW5ndGgobGV2ZWxzKGZhY3RvcihkX3VzX2FkX3BpbG90X3JhdyRzdWJpZCkpKSksCiAgICAgICAgICAgICAgICAgICAgICAgInRhcmdldCIsCiAgICAgICAgICAgICAgICAgICAgICAgY2hhcmFjdGVyLAogICAgICAgICAgICAgICAgICAgICAgIHNlcCA9ICJfIikpICU+JQogIGNvbHVtbl90b19yb3duYW1lcygic3ViaWQiKSAlPiUKICBzZWxlY3QoLWBhZGQgYW5kIHN1YnRyYWN0IG51bWJlcnNgLCAtY2hhcmFjdGVyKQpgYGAKCmBgYHtyLCBpbmNsdWRlID0gRiwgd2FybmluZyA9IEZBTFNFfQojIyBVUyBhZHVsdHM6IE5PVCBZRVQgUlVOCiMjIFVTIGNoaWxkcmVuOiBOT1QgWUVUIFJVTgoKIyMgR0ggYWR1bHRzOiBOT1QgWUVUIFJVTgpkX2doX2FkIDwtIHJlYWQuY3N2KCIvVXNlcnMva3dlaXNtYW4vRGVza3RvcC9URU1QL1RFTVBfR0hBTkFfMjAxOC9iZWV0bGVzX2doYW5hX2FkdWx0c190aWR5XzIwMTgtMDgtMTIuY3N2IikgJT4lIGNsZWFuX2Z1bihrZXkgPSBxdWVzdGlvbl9rZXksIGV4X2FkZHN1YiA9IFQsIHNpdGUgPSAiZ2giLCBhZ2UgPSAiYWQiKQojIyBHSCBjaGlsZHJlbgpkX2doX2NoIDwtIHJlYWQuY3N2KCIvVXNlcnMva3dlaXNtYW4vRGVza3RvcC9URU1QL1RFTVBfR0hBTkEvYmVldGxlc19naGFuYV90aWR5XzIwMTctMDctMTIuY3N2IikgJT4lIGNsZWFuX2Z1bihrZXkgPSBxdWVzdGlvbl9rZXksIGV4X2FkZHN1YiA9IFQsIHNpdGUgPSAiZ2giLCBhZ2UgPSAiY2giKQpkX2doX2NoX2ZhbnRlIDwtIHJlYWQuY3N2KCIvVXNlcnMva3dlaXNtYW4vRGVza3RvcC9URU1QL1RFTVBfR0hBTkFfMjAxOC9iZWV0bGVzX2doYW5hX2ZhbnRlX2NoaWxkcmVuX3RpZHlfMjAxOC0wNy0xOS5jc3YiKVstMV0gJT4lIAogIHJlbmFtZShzdWJudW0gPSBzdWJpZCkgJT4lIAogIGZpbHRlcihncmVwbCgiZmFudGUiLCB0b2xvd2VyKGxhbmd1YWdlX2hvbWUpKSB8IGdyZXBsKCJ0d2kiLCB0b2xvd2VyKGxhbmd1YWdlX2hvbWUpKSkgJT4lCiAgY2xlYW5fZnVuKGtleSA9IHF1ZXN0aW9uX2tleSwgZXhfYWRkc3ViID0gVCwgc2l0ZSA9ICJnaCIsIGFnZSA9ICJjaCIpCgojIyBDSCBhZHVsdHM6IE5PVCBZRVQgUlVOCiMjIENIIGNoaWxkcmVuOiBOT1QgWUVUIFJVTgoKIyMgVEggYWR1bHRzCmRfdGhfYWQgPC0gcmVhZC5jc3YoIi9Vc2Vycy9rd2Vpc21hbi9EZXNrdG9wL1RFTVAvVEVNUF9USEFJTEFORC9iZWV0bGVzX3RoYWlsYW5kX2FkdWx0c190aWR5XzIwMTgtMDUtMDkuY3N2IikgJT4lIGNsZWFuX2Z1bihrZXkgPSBxdWVzdGlvbl9rZXksIGV4X2FkZHN1YiA9IFQsIHNpdGUgPSAidGgiLCBhZ2UgPSAiYWQiKQojIyBUSCBjaGlsZHJlbgpkX3RoX2NoIDwtIHJlYWQuY3N2KCIvVXNlcnMva3dlaXNtYW4vRGVza3RvcC9URU1QL1RFTVBfVEhBSUxBTkQvYmVldGxlc190aGFpbGFuZF9jaGlsZHJlbl90aWR5XzIwMTgtMDUtMDkuY3N2IikgJT4lIGNsZWFuX2Z1bihrZXkgPSBxdWVzdGlvbl9rZXksIGV4X2FkZHN1YiA9IFQsIHNpdGUgPSAidGgiLCBhZ2UgPSAiY2giKQoKIyMgVlQgYWR1bHRzCmRfdnRfYWQgPC0gcmVhZC5jc3YoIi9Vc2Vycy9rd2Vpc21hbi9EZXNrdG9wL1RFTVAvVEVNUF9WQU5VQVRVL2JlZXRsZXNfdmFudWF0dV9hZHVsdHNfdGlkeV8yMDE4LTA1LTA5LmNzdiIpICU+JSBjbGVhbl9mdW4oa2V5ID0gcXVlc3Rpb25fa2V5LCBleF9hZGRzdWIgPSBULCBzaXRlID0gInZ0IiwgYWdlID0gImFkIikKIyMgVlQgY2hpbGRyZW4KZF92dF9jaCA8LSByZWFkLmNzdigiL1VzZXJzL2t3ZWlzbWFuL0Rlc2t0b3AvVEVNUC9URU1QX1ZBTlVBVFUvYmVldGxlc192YW51YXR1X2NoaWxkcmVuX3RpZHlfMjAxOC0wNS0wOS5jc3YiKSAlPiUgY2xlYW5fZnVuKGtleSA9IHF1ZXN0aW9uX2tleSwgZXhfYWRkc3ViID0gVCwgc2l0ZSA9ICJ2dCIsIGFnZSA9ICJjaCIpCmBgYAoKYGBge3J9CmRfYWxsIDwtICMgZF91c19hZF9waWxvdCAlPiUgcm93bmFtZXNfdG9fY29sdW1uKCJzdWJpZCIpICU+JQogIGRfZ2hfYWQgJT4lIHJvd25hbWVzX3RvX2NvbHVtbigic3ViaWQiKSAlPiUKICBmdWxsX2pvaW4oZF9naF9jaCAlPiUgcm93bmFtZXNfdG9fY29sdW1uKCJzdWJpZCIpKSAlPiUKICBmdWxsX2pvaW4oZF90aF9hZCAlPiUgcm93bmFtZXNfdG9fY29sdW1uKCJzdWJpZCIpKSAlPiUKICBmdWxsX2pvaW4oZF90aF9jaCAlPiUgcm93bmFtZXNfdG9fY29sdW1uKCJzdWJpZCIpKSAlPiUKICBmdWxsX2pvaW4oZF92dF9hZCAlPiUgcm93bmFtZXNfdG9fY29sdW1uKCJzdWJpZCIpKSAlPiUKICBmdWxsX2pvaW4oZF92dF9jaCAlPiUgcm93bmFtZXNfdG9fY29sdW1uKCJzdWJpZCIpKSAlPiUKICBjb2x1bW5fdG9fcm93bmFtZXMoInN1YmlkIikKYGBgCgojIFNoYXJlZCBjb25jZXB0dWFsIHN0cnVjdHVyZQoKUG9vbGluZyBhbGwgcGFydGljaXBhbnRzIGZyb20gYWxsIHNpdGVzIHRvZ2V0aGVyIGludG8gYSBjb21tb24gZmFjdG9yIHN0cnVjdHVyZS4KCiMjIFBhcmFsbGVsIGFuYWx5c2lzCgojIyMgSG93IG1hbnkgZmFjdG9ycyB0byByZXRhaW4/CgpgYGB7cn0KcmV0ZW5fYWxsX1BBIDwtIGZhLnBhcmFsbGVsKGRfYWxsLCBwbG90ID0gRik7IHJldGVuX2FsbF9QQQpyZXRlbl9hbGxfcGFyIDwtIHJldGVuX2FsbF9QQSRuZmFjdApgYGAKCiMjIyBXaGF0IGFyZSB0aGVzZSBmYWN0b3JzPwoKYGBge3J9CmVmYV9hbGxfcGFyIDwtIGZhKGRfYWxsLCBuZmFjdG9ycyA9IHJldGVuX2FsbF9wYXIsIHJvdGF0ZSA9ICJvYmxpbWluIiwKICAgICAgICAgICAgICAgICAgc2NvcmVzID0gInRlbkJlcmdlIiwgaW1wdXRlID0gIm1lZGlhbiIpCmBgYAoKYGBge3IsIGZpZy53aWR0aCA9IDQuMiwgZmlnLmFzcCA9IDAuN30KaGVhdG1hcF9mdW4oZWZhX2FsbF9wYXIsIAogICAgICAgICAgICBmYWN0b3JfbmFtZXMgPSBjKCJDT0dOSVRJVkUiLCAiQk9ESUxZIiwgCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIlNPQ0lBTC1FTU9USU9OQUwiLCAiW290aGVyXSIpKSArIAogIGxhYnModGl0bGUgPSAiRmFjdG9yIGxvYWRpbmdzIChkYXRhIHBvb2xlZCBhY3Jvc3MgYWxsIHNhbXBsZXMpIikKYGBgCgojIyMgV2hpY2ggY2FwYWNpdGllcyBhcmUgYXR0cmlidXRlZCB0byB3aGljaCB0YXJnZXRzPwoKIyMjIyBGYWN0b3Igc2NvcmVzCgpgYGB7ciwgZmlnLndpZHRoID0gNSwgZmlnLmFzcCA9IDAuOH0Kc2NvcmVzcGxvdF9mdW4oZWZhX2FsbF9wYXIsIHRhcmdldCA9ICJhbGwiLAogICAgICAgICAgICAgICBmYWN0b3JfbmFtZXMgPSBjKCJDT0dOSVRJVkUiLCAiQk9ESUxZIiwgCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIlNPQ0lBTC1FTU9USU9OQUwiLCAiW290aGVyXSIpKSArIAogIGxhYnModGl0bGUgPSAiRmFjdG9yIHNjb3JlcyAoYnkgc2FtcGxlLCBmYWN0b3IsIGFuZCB0YXJnZXQgZW50aXR5KSIsCiAgICAgICBzdWJ0aXRsZSA9ICJBbGwgdGFyZ2V0cyIpCmBgYAoKYGBge3IsIGZpZy53aWR0aCA9IDMuNSwgZmlnLmFzcCA9IDAuOH0Kc2NvcmVzcGxvdF9mdW4oZWZhX2FsbF9wYXIsIHRhcmdldCA9IGMoImdob3N0cyIsICJHb2QiLCAiY2hpbGRyZW4iKSwKICAgICAgICAgICAgICAgZmFjdG9yX25hbWVzID0gYygiQ09HTklUSVZFIiwgIkJPRElMWSIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIlNPQy4tRU1PLiIsICJbb3RoZXJdIikpICsgCiAgbGFicyh0aXRsZSA9ICJGYWN0b3Igc2NvcmVzIChieSBzYW1wbGUsIGZhY3RvciwgYW5kIHRhcmdldCBlbnRpdHkpIiwKICAgICAgIHN1YnRpdGxlID0gIkh1bWFuIGFuZCAnc3VwZXJuYXR1cmFsJyB0YXJnZXRzIG9ubHkiKQpgYGAKCmBgYHtyLCBmaWcud2lkdGggPSA1LCBmaWcuYXNwID0gMX0KaXRlbXNwbG90X2Z1bihlZmFfYWxsX3BhciwgdGFyZ2V0ID0gYygiZ2hvc3RzIiwgIkdvZCIsICJjaGlsZHJlbiIpKSArCiAgbGFicyh0aXRsZSA9ICJQYXJhbGxlbCBBbmFseXNpcyIpCmBgYAoKIyMjIyBTdW1tYXJ5IHNjb3JlcwoKYGBge3J9CmZhY3RvcnNfcGFyIDwtIGVmYV9hbGxfcGFyJGxvYWRpbmdzW10gJT4lCiAgZGF0YS5mcmFtZSgpICU+JQogIHJvd25hbWVzX3RvX2NvbHVtbigiY2FwYWNpdHkiKSAlPiUKICBnYXRoZXIoZmFjdG9yLCBsb2FkaW5nLCAtY2FwYWNpdHkpICU+JQogIGdyb3VwX2J5KGNhcGFjaXR5KSAlPiUKICB0b3BfbigxLCBsb2FkaW5nKSAlPiUKICB1bmdyb3VwKCkgJT4lCiAgYXJyYW5nZShmYWN0b3IsIGRlc2MobG9hZGluZykpICU+JQogIG11dGF0ZShvcmRlciA9IDE6bnJvdyguKSkKCmZhY3RvcnNfcGFyX2hvd21hbnkgPC0gZmFjdG9yc19wYXIgJT4lCiAgY291bnQoZmFjdG9yKQoKZmFjdG9yc19wYXJfY3VsbGVkIDwtIGZhY3RvcnNfcGFyICU+JQogIGdyb3VwX2J5KGZhY3RvcikgJT4lCiAgdG9wX24obWluKGZhY3RvcnNfcGFyX2hvd21hbnkkbiksIGxvYWRpbmcpICU+JQogIHVuZ3JvdXAoKSAlPiUKICBhcnJhbmdlKGZhY3RvciwgZGVzYyhsb2FkaW5nKSkgJT4lCiAgbXV0YXRlKG9yZGVyID0gMTpucm93KC4pKQoKc2NvcmVzX3Bhcl9wcmVsaW0gPC0gZF9hbGwgJT4lCiAgcm93bmFtZXNfdG9fY29sdW1uKCJzaXRlX2FnZV9zdWJpZF90YXJnZXRfZW50aXR5IikgJT4lCiAgZ2F0aGVyKGNhcGFjaXR5LCByZXNwb25zZSwgLXNpdGVfYWdlX3N1YmlkX3RhcmdldF9lbnRpdHkpICU+JQogIG11dGF0ZShzaXRlID0gZ3N1YigiXy4qJCIsICIiLCBzaXRlX2FnZV9zdWJpZF90YXJnZXRfZW50aXR5KSwKICAgICAgICAgYWdlID0gZ3N1YigiXy4qJCIsICIiLCBnc3ViKCJeLi5fIiwgIiIsIHNpdGVfYWdlX3N1YmlkX3RhcmdldF9lbnRpdHkpKSwKICAgICAgICAgc3ViaWQgPSBnc3ViKCJfdGFyZ2V0LiokIiwgIiIsIHNpdGVfYWdlX3N1YmlkX3RhcmdldF9lbnRpdHkpLAogICAgICAgICB0YXJnZXQgPSBnc3ViKCJeLip0YXJnZXRfIiwgIiIsIHNpdGVfYWdlX3N1YmlkX3RhcmdldF9lbnRpdHkpKSAlPiUKICBtdXRhdGUodGFyZ2V0ID0gY2FzZV93aGVuKHRhcmdldCA9PSAicGlncyIgfiBOQV9jaGFyYWN0ZXJfLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgdGFyZ2V0ID09ICJOQSIgfiBOQV9jaGFyYWN0ZXJfLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgdGFyZ2V0ID09ICJjcmlja2V0cyIgfiAiYmVldGxlcyIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBUUlVFIH4gdGFyZ2V0KSkgJT4lCiAgbXV0YXRlKHNpdGUgPSBmYWN0b3Ioc2l0ZSwgbGV2ZWxzID0gYygidXMiLCAiZ2giLCAidGgiLCAiY2giLCAidnQiKSwKICAgICAgICAgICAgICAgICAgICAgICBsYWJlbHMgPSBjKCJVUyIsICJHaGFuYSIsICJUaGFpbGFuZCIsICJDaGluYSIsICJWYW51YXR1IikpLAogICAgICAgICBhZ2UgPSBmYWN0b3IoYWdlLCBsZXZlbHMgPSBjKCJhZCIsICJjaCIpLAogICAgICAgICAgICAgICAgICAgICAgbGFiZWxzID0gYygiYWR1bHRzIiwgImNoaWxkcmVuIikpLAogICAgICAgICB0YXJnZXQgPSBmYWN0b3IodGFyZ2V0LAogICAgICAgICAgICAgICAgICAgICAgICAgbGV2ZWxzID0gYygicm9ja3MiLCAiZmxvd2VycyIsICJjZWxsIHBob25lcyIsIAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAiYmVldGxlcyIsICJjaGlja2VucyIsICJtaWNlIiwgCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICJkb2dzIiwgImNoaWxkcmVuIiwgCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICJnaG9zdHMiLCAiR29kIikpKSAlPiUKICBzZWxlY3QoLXNpdGVfYWdlX3N1YmlkX3RhcmdldF9lbnRpdHkpICU+JQogIGZ1bGxfam9pbihmYWN0b3JzX3Bhcl9jdWxsZWQpICU+JQogICMgZnVsbF9qb2luKGZhY3RvcnNfcGFyKSAlPiUKICBtdXRhdGUoZmFjdG9yID0gZmFjdG9yKGZhY3RvciwgbGV2ZWxzID0gYygiTVIyIiwgIk1SMSIsICJNUjMiLCAiTVI0IiksCiAgICAgICAgICAgICAgICAgICAgICAgICBsYWJlbHMgPSBjKCJCT0RJTFkiLCAiQ09HTklUSVZFIiwgCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICJTT0NJQUwtRU1PVElPTkFMIiwgIltvdGhlcl0iKSkpICU+JQogIGZpbHRlcighaXMubmEodGFyZ2V0KSwgIWlzLm5hKGZhY3RvcikpICU+JQogIGRpc3RpbmN0KCkKCnNjb3Jlc19wYXIgPC0gc2NvcmVzX3Bhcl9wcmVsaW0gJT4lCiAgZ3JvdXBfYnkoc2l0ZSwgYWdlLCBzdWJpZCwgdGFyZ2V0LCBmYWN0b3IpICU+JQogIHN1bW1hcmlzZShzY29yZSA9IG1lYW4ocmVzcG9uc2UsIG5hLnJtID0gVCkpICU+JQogIHVuZ3JvdXAoKQoKc2NvcmVzX3Bhcl9tYiA8LSBzY29yZXNfcGFyICU+JSAKICBncm91cF9ieShzaXRlLCBhZ2UsIHRhcmdldCwgZmFjdG9yKSAlPiUKICBtdWx0aV9ib290X3N0YW5kYXJkKGNvbCA9ICJzY29yZSIsIG5hLnJtID0gVCkgJT4lCiAgdW5ncm91cCgpCmBgYAoKYGBge3J9CiMgY2FsY3VsYXRlIHJlbGlhYmlsaXR5CnNjb3Jlc19wYXJfcHJlbGltX3dpZGUgPC0gc2NvcmVzX3Bhcl9wcmVsaW0gJT4lCiAgZnVsbF9qb2luKGZhY3RvcnNfcGFyX2N1bGxlZCkgJT4lCiAgZmlsdGVyKCFpcy5uYShmYWN0b3IpLCAhaXMubmEoc3ViaWQpKSAlPiUgCiAgYXJyYW5nZShmYWN0b3IsIGRlc2MobG9hZGluZykpICU+JQogIHNlbGVjdChzdWJpZCwgY2FwYWNpdHksIHJlc3BvbnNlKSAlPiUKICBzcHJlYWQoY2FwYWNpdHksIHJlc3BvbnNlKSAlPiUKICBzZWxlY3Qoc3ViaWQsIGZhY3RvcnNfcGFyX2N1bGxlZCRjYXBhY2l0eSkgJT4lCiAgY29sdW1uX3RvX3Jvd25hbWVzKCJzdWJpZCIpCgojIEJPRElMWQphbHBoYShzY29yZXNfcGFyX3ByZWxpbV93aWRlWzU6OF0pJHRvdGFsCgojICJDT0dOSVRJVkUiCmFscGhhKHNjb3Jlc19wYXJfcHJlbGltX3dpZGVbMTo0XSkkdG90YWwKCiMgIlNPQ0lBTC1FTU9USU9OQUwiCmFscGhhKHNjb3Jlc19wYXJfcHJlbGltX3dpZGVbOToxMl0pJHRvdGFsCmBgYAoKCmBgYHtyLCBmaWcud2lkdGggPSA1LCBmaWcuYXNwID0gMC44fQpnZ3Bsb3Qoc2NvcmVzX3BhciwgYWVzKHggPSB0YXJnZXQsIHkgPSBzY29yZSwgY29sb3IgPSBmYWN0b3IpKSArCiAgZmFjZXRfZ3JpZChjb2xzID0gdmFycyhzaXRlLCBhZ2UpLCByb3dzID0gdmFycyhmYWN0b3IpKSArCiAgZ2VvbV9qaXR0ZXIoaGVpZ2h0ID0gMC4wMiwgd2lkdGggPSAwLjIsIGFscGhhID0gMC4yLCBzaG93LmxlZ2VuZCA9IEYpICsKICBnZW9tX3BvaW50cmFuZ2UoZGF0YSA9IHNjb3Jlc19wYXJfbWIsCiAgICAgICAgICAgICAgICAgIGFlcyh5ID0gbWVhbiwgeW1pbiA9IGNpX2xvd2VyLCB5bWF4ID0gY2lfdXBwZXIpLAogICAgICAgICAgICAgICAgICBmYXR0ZW4gPSAyLCBjb2xvciA9ICJibGFjayIpICsKICBzY2FsZV9jb2xvcl9icmV3ZXIocGFsZXR0ZSA9ICJTZXQxIikgKwogIHRoZW1lKGF4aXMudGV4dC54ID0gZWxlbWVudF90ZXh0KGFuZ2xlID0gNDUsIGhqdXN0ID0gMSwgdmp1c3QgPSAxKSkKYGBgCgpgYGB7ciwgZmlnLndpZHRoID0gMy41LCBmaWcuYXNwID0gMC44fQpnZ3Bsb3Qoc2NvcmVzX3BhciAlPiUgZmlsdGVyKHRhcmdldCAlaW4lIGMoImNoaWxkcmVuIiwgImdob3N0cyIsICJHb2QiKSksIAogICAgICAgYWVzKHggPSB0YXJnZXQsIHkgPSBzY29yZSwgY29sb3IgPSBmYWN0b3IpKSArCiAgZmFjZXRfZ3JpZChjb2xzID0gdmFycyhzaXRlLCBhZ2UpLCByb3dzID0gdmFycyhmYWN0b3IpKSArCiAgZ2VvbV9qaXR0ZXIoaGVpZ2h0ID0gMC4wMiwgd2lkdGggPSAwLjIsIGFscGhhID0gMC4yNSwgc2hvdy5sZWdlbmQgPSBGKSArCiAgZ2VvbV9wb2ludHJhbmdlKGRhdGEgPSBzY29yZXNfcGFyX21iICU+JQogICAgICAgICAgICAgICAgICAgIGZpbHRlcih0YXJnZXQgJWluJSBjKCJjaGlsZHJlbiIsICJnaG9zdHMiLCAiR29kIikpLAogICAgICAgICAgICAgICAgICBhZXMoeSA9IG1lYW4sIHltaW4gPSBjaV9sb3dlciwgeW1heCA9IGNpX3VwcGVyKSwKICAgICAgICAgICAgICAgICAgZmF0dGVuID0gMiwgY29sb3IgPSAiYmxhY2siKSArCiAgc2NhbGVfY29sb3JfYnJld2VyKHBhbGV0dGUgPSAiU2V0MSIpICsKICB0aGVtZShheGlzLnRleHQueCA9IGVsZW1lbnRfdGV4dChhbmdsZSA9IDQ1LCBoanVzdCA9IDEsIHZqdXN0ID0gMSkpCmBgYAoKCiMjIE1pbmltaXppbmcgQklDCgojIyMgSG93IG1hbnkgZmFjdG9ycyB0byByZXRhaW4/CgpgYGB7cn0KcmV0ZW5fYWxsX0JJQyA8LSBWU1MoZF9hbGwsIHBsb3QgPSBGKTsgcmV0ZW5fYWxsX0JJQwpyZXRlbl9hbGxfYmljIDwtIGRhdGEuZnJhbWUocmV0ZW5fYWxsX0JJQyR2c3Muc3RhdHMgJT4lIHJvd25hbWVzX3RvX2NvbHVtbigibmZhY3QiKSAlPiUgdG9wX24oLTEsIEJJQykpJG5mYWN0ICU+JSBhcy5udW1lcmljKCkKYGBgCgojIyMgV2hhdCBhcmUgdGhlc2UgZmFjdG9ycz8KCmBgYHtyfQplZmFfYWxsX2JpYyA8LSBmYShkX2FsbCwgbmZhY3RvcnMgPSByZXRlbl9hbGxfYmljLCByb3RhdGUgPSAib2JsaW1pbiIsCiAgICAgICAgICAgICAgICAgIHNjb3JlcyA9ICJ0ZW5CZXJnZSIsIGltcHV0ZSA9ICJtZWRpYW4iKQpgYGAKCmBgYHtyLCBmaWcud2lkdGggPSA0LjV9CmhlYXRtYXBfZnVuKGVmYV9hbGxfYmljLCAKICAgICAgICAgICAgZmFjdG9yX25hbWVzID0gYygiQ09HTklUSVZFIiwgIkJPRElMWSIsICJTT0NJQUwtRU1PVElPTkFMIiwgIm90aGVyIikpICsgCiAgIyBsYWJzKHRpdGxlID0gIk1pbmltaXppbmcgQklDIikKICBsYWJzKHggPSAiRmlndXJlIDE6IFNoYXJlZCBjb25jZXB0dWFsIHN0cnVjdHVyZSIpICsKICB0aGVtZShheGlzLnRpdGxlLnggPSBlbGVtZW50X3RleHQoaGp1c3QgPSAwKSkgKwogIGd1aWRlcyhmaWxsID0gZ3VpZGVfY29sb3JiYXIoImZhY3RvciBsb2FkaW5nIiwgYmFyaGVpZ2h0ID0gMTUpKQpgYGAKCiMjIyBXaGljaCBjYXBhY2l0aWVzIGFyZSBhdHRyaWJ1dGVkIHRvIHdoaWNoIHRhcmdldHM/CgpgYGB7ciwgZmlnLndpZHRoID0gNSwgZmlnLmFzcCA9IDF9CnNjb3Jlc3Bsb3RfZnVuKGVmYV9hbGxfYmljLCB0YXJnZXQgPSAiYWxsIiwgaGlnaGxpZ2h0ID0gInN1cGVybmF0dXJhbCIsCiAgICAgICAgICAgIGZhY3Rvcl9uYW1lcyA9IGMoIkNPR05JVElWRSIsICJCT0RJTFkiLCAiU09DSUFMLUVNT1RJT05BTCIsICJvdGhlciIpKSArIAogIHRoZW1lKGF4aXMudGV4dC54ID0gZWxlbWVudF90ZXh0KGFuZ2xlID0gOTAsIGhqdXN0ID0gMSwgdmp1c3QgPSAxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbG9yID0gYyhyZXAoImJsYWNrIiwgOCksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlcCgiIzk4NGVhMyIsIDIpKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBmYWNlID0gYyhyZXAoInBsYWluIiwgOCksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcmVwKCJib2xkIiwgMikpKSkgKwogIHNjYWxlX2ZpbGxfbWFudWFsKHZhbHVlcyA9IGMoIiNlNDFhMWMiLCAiIzRkYWY0YSIsICIjMzc3ZWI4IiwgImdyYXkiKSkgKwogICMgbGFicyh0aXRsZSA9ICJNaW5pbWl6aW5nIEJJQyIpCiAgbGFicyh0aXRsZSA9ICJGaWd1cmUgMjogRmFjdG9yIHNjb3JlcyIpCmBgYAoKYGBge3IsIGZpZy53aWR0aCA9IDMuNSwgZmlnLmFzcCA9IDF9CnNjb3Jlc3Bsb3RfZnVuKGVmYV9hbGxfYmljLCB0YXJnZXQgPSBjKCJnaG9zdHMiLCAiR29kIiwgImNoaWxkcmVuIikpICsgCiAgIyBzY2FsZV9maWxsX21hbnVhbCh2YWx1ZXMgPSBjKCIjZTQxYTFjIiwgIiM0ZGFmNGEiLCAiIzM3N2ViOCIpKSArCiAgbGFicyh0aXRsZSA9ICJNaW5pbWl6aW5nIEJJQyIpCmBgYAoKYGBge3IsIGZpZy53aWR0aCA9IDUsIGZpZy5hc3AgPSAxfQppdGVtc3Bsb3RfZnVuKGVmYV9hbGxfYmljLCB0YXJnZXQgPSBjKCJnaG9zdHMiLCAiR29kIiwgImNoaWxkcmVuIikpICsgCiAgbGFicyh0aXRsZSA9ICJNaW5pbWl6aW5nIEJJQyIpCmBgYAoKCgojIyBQcmVzZXQgY3JpdGVyaWEKCiMjIyBIb3cgbWFueSBmYWN0b3JzIHRvIHJldGFpbj8KCmBgYHtyfQpyZXRlbl9hbGxfayA8LSByZXRlbl9mdW4oZF9hbGwsIHJvdF90eXBlID0gIm9ibGltaW4iKTsgcmV0ZW5fYWxsX2sKYGBgCgojIyMgV2hhdCBhcmUgdGhlc2UgZmFjdG9ycz8KCmBgYHtyfQplZmFfYWxsX2sgPC0gZmEoZF9hbGwsIG5mYWN0b3JzID0gcmV0ZW5fYWxsX2ssIHJvdGF0ZSA9ICJvYmxpbWluIiwKICAgICAgICAgICAgICAgICAgc2NvcmVzID0gInRlbkJlcmdlIiwgaW1wdXRlID0gIm1lZGlhbiIpCmBgYAoKYGBge3IsIGZpZy53aWR0aCA9IDMsIGZpZy5hc3AgPSAyfQpoZWF0bWFwX2Z1bihlZmFfYWxsX2spICsgCiAgbGFicyh0aXRsZSA9ICJQcmVzZXQgY3JpdGVyaWEgKFdlaXNtYW4gZXQgYWwuLCAyMDE3KSIpCmBgYAoKIyMjIFdoaWNoIGNhcGFjaXRpZXMgYXJlIGF0dHJpYnV0ZWQgdG8gd2hpY2ggdGFyZ2V0cz8KCmBgYHtyLCBmaWcud2lkdGggPSA2LCBmaWcuYXNwID0gMC44fQpzY29yZXNwbG90X2Z1bihlZmFfYWxsX2ssIHRhcmdldCA9ICJhbGwiKSArIAogIGxhYnModGl0bGUgPSAiUHJlc2V0IGNyaXRlcmlhIChXZWlzbWFuIGV0IGFsLiwgMjAxNykiKQpgYGAKCmBgYHtyLCBmaWcud2lkdGggPSAzLCBmaWcuYXNwID0gMS41fQpzY29yZXNwbG90X2Z1bihlZmFfYWxsX2ssIHRhcmdldCA9IGMoImdob3N0cyIsICJHb2QiLCAiY2hpbGRyZW4iKSkgKyAKICBsYWJzKHRpdGxlID0gIlByZXNldCBjcml0ZXJpYSAoV2Vpc21hbiBldCBhbC4sIDIwMTcpIikKYGBgCgpgYGB7ciwgZmlnLndpZHRoID0gNSwgZmlnLmFzcCA9IDF9Cml0ZW1zcGxvdF9mdW4oZWZhX2FsbF9rLCB0YXJnZXQgPSBjKCJnaG9zdHMiLCAiR29kIiwgImNoaWxkcmVuIikpICsgCiAgbGFicyh0aXRsZSA9ICJQcmVzZXQgY3JpdGVyaWEgKFdlaXNtYW4gZXQgYWwuLCAyMDE3KSIpCmBgYAoKCiMjIDMgZmFjdG9ycwoKIyMjIFdoYXQgYXJlIHRoZXNlIGZhY3RvcnM/CgpgYGB7cn0KZWZhX2FsbF8zIDwtIGZhKGRfYWxsLCBuZmFjdG9ycyA9IDMsIHJvdGF0ZSA9ICJvYmxpbWluIiwKICAgICAgICAgICAgICAgIHNjb3JlcyA9ICJ0ZW5CZXJnZSIsIGltcHV0ZSA9ICJtZWRpYW4iKQpgYGAKCmBgYHtyLCBmaWcud2lkdGggPSA0LCBmaWcuYXNwID0gMC42fQpoZWF0bWFwX2Z1bihlZmFfYWxsXzMsIAogICAgICAgICAgICBmYWN0b3JfbmFtZXMgPSBjKCJDT0dOSVRJVkUiLCAiQk9ESUxZIiwgIlNPQ0lBTC1FTU9USU9OQUwiKSkgKyAKICBsYWJzKHggPSAiU2hhcmVkIGNvbmNwZXR1YWwgc3RydWN0dXJlIikgKwogIHRoZW1lKGF4aXMudGl0bGUueCA9IGVsZW1lbnRfdGV4dChoanVzdCA9IDApKQogICMgbGFicyh0aXRsZSA9ICJQcmVzZXQgY3JpdGVyaWEgKFdlaXNtYW4gZXQgYWwuLCAyMDE3KSIpCmBgYAoKIyMjIFdoaWNoIGNhcGFjaXRpZXMgYXJlIGF0dHJpYnV0ZWQgdG8gd2hpY2ggdGFyZ2V0cz8KCmBgYHtyLCBmaWcud2lkdGggPSA2LCBmaWcuYXNwID0gMC42N30Kc2NvcmVzcGxvdF9mdW4oZWZhX2FsbF8zLCB0YXJnZXQgPSAiYWxsIiwgaGlnaGxpZ2h0ID0gInN1cGVybmF0dXJhbCIsCiAgICAgICAgICAgICAgIGZhY3Rvcl9uYW1lcyA9IGMoIkNPR05JVElWRSIsICJCT0RJTFkiLCAiU09DSUFMLUVNT1RJT05BTCIpKSArCiAgc2NhbGVfZmlsbF9tYW51YWwodmFsdWVzID0gYygiI2U0MWExYyIsICIjNGRhZjRhIiwgIiMzNzdlYjgiKSkgKwogIHRoZW1lKGF4aXMudGV4dC54ID0gZWxlbWVudF90ZXh0KGFuZ2xlID0gOTAsIGhqdXN0ID0gMSwgdmp1c3QgPSAxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbG9yID0gYyhyZXAoImJsYWNrIiwgOCksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlcCgiIzk4NGVhMyIsIDIpKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBmYWNlID0gYyhyZXAoInBsYWluIiwgOCksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcmVwKCJib2xkIiwgMikpKSkKYGBgCgpgYGB7ciwgZmlnLndpZHRoID0gMywgZmlnLmFzcCA9IDEuNX0Kc2NvcmVzcGxvdF9mdW4oZWZhX2FsbF8zLCB0YXJnZXQgPSBjKCJnaG9zdHMiLCAiR29kIiwgImNoaWxkcmVuIikpICsgCiAgbGFicyh0aXRsZSA9ICJQcmVzZXQgY3JpdGVyaWEgKFdlaXNtYW4gZXQgYWwuLCAyMDE3KSIpCmBgYAoKYGBge3IsIGZpZy53aWR0aCA9IDUsIGZpZy5hc3AgPSAxfQppdGVtc3Bsb3RfZnVuKGVmYV9hbGxfMywgdGFyZ2V0ID0gYygiZ2hvc3RzIiwgIkdvZCIsICJjaGlsZHJlbiIpKSArIAogIGxhYnModGl0bGUgPSAiUHJlc2V0IGNyaXRlcmlhIChXZWlzbWFuIGV0IGFsLiwgMjAxNykiKQpgYGAKCgojIENvbXBhcmluZyBjb25jZXB0dWFsIHN0cnVjdHVyZXMKCldlJ2xsIGV4dHJhY3QgNCBmYWN0b3JzIGZyb20gYWxsIHNhbXBsZXMsIHRvIGtlZXAgdGhpbmdzIHNpbXBsZS4KCmBgYHtyfQplZmFfdXNfYWRfNCA8LSBmYShkX3VzX2FkX3BpbG90LCBuZmFjdG9ycyA9IDQsIHJvdGF0ZSA9ICJvYmxpbWluIikKZWZhX2doX2FkXzQgPC0gZmEoZF9naF9hZCwgbmZhY3RvcnMgPSA0LCByb3RhdGUgPSAib2JsaW1pbiIpCmVmYV9naF9jaF80IDwtIGZhKGRfZ2hfY2gsIG5mYWN0b3JzID0gNCwgcm90YXRlID0gIm9ibGltaW4iKQplZmFfdGhfYWRfNCA8LSBmYShkX3RoX2FkLCBuZmFjdG9ycyA9IDQsIHJvdGF0ZSA9ICJvYmxpbWluIikKZWZhX3RoX2NoXzQgPC0gZmEoZF90aF9jaCwgbmZhY3RvcnMgPSA0LCByb3RhdGUgPSAib2JsaW1pbiIpCmVmYV92dF9hZF80IDwtIGZhKGRfdnRfYWQsIG5mYWN0b3JzID0gNCwgcm90YXRlID0gIm9ibGltaW4iKQplZmFfdnRfY2hfNCA8LSBmYShkX3Z0X2NoLCBuZmFjdG9ycyA9IDQsIHJvdGF0ZSA9ICJvYmxpbWluIikKYGBgCgpgYGB7cn0KcGxvdF91c19hZF80IDwtIGhlYXRtYXBfZnVuKGVmYV91c19hZF80KSArIAogIGd1aWRlcyhmaWxsID0gIm5vbmUiKSArIAogIGxhYnMoeCA9ICJVUzogYWR1bHRzIikgKwogIHRoZW1lKGF4aXMudGl0bGUueCA9IGVsZW1lbnRfdGV4dChoanVzdCA9IDApKQoKcGxvdF9naF9hZF80IDwtIGhlYXRtYXBfZnVuKGVmYV9naF9hZF80KSArIAogIGd1aWRlcyhmaWxsID0gIm5vbmUiKSArIAogIGxhYnMoeCA9ICJHaGFuYTogYWR1bHRzIikgKwogIHRoZW1lKGF4aXMudGl0bGUueCA9IGVsZW1lbnRfdGV4dChoanVzdCA9IDApKQoKcGxvdF9naF9jaF80IDwtIGhlYXRtYXBfZnVuKGVmYV9naF9jaF80KSArIAogIGd1aWRlcyhmaWxsID0gIm5vbmUiKSArIAogIGxhYnMoeCA9ICJHaGFuYTogY2hpbGRyZW4iKSArCiAgdGhlbWUoYXhpcy50aXRsZS54ID0gZWxlbWVudF90ZXh0KGhqdXN0ID0gMCkpCgpwbG90X3RoX2FkXzQgPC0gaGVhdG1hcF9mdW4oZWZhX3RoX2FkXzQpICsgCiAgZ3VpZGVzKGZpbGwgPSAibm9uZSIpICsgCiAgbGFicyh4ID0gIlRoYWlsYW5kOiBhZHVsdHMiKSArCiAgdGhlbWUoYXhpcy50aXRsZS54ID0gZWxlbWVudF90ZXh0KGhqdXN0ID0gMCkpCgpwbG90X3RoX2NoXzQgPC0gaGVhdG1hcF9mdW4oZWZhX3RoX2NoXzQpICsgCiAgZ3VpZGVzKGZpbGwgPSAibm9uZSIpICsgCiAgbGFicyh4ID0gIlRoYWlsYW5kOiBjaGlsZHJlbiIpICsKICB0aGVtZShheGlzLnRpdGxlLnggPSBlbGVtZW50X3RleHQoaGp1c3QgPSAwKSkKCnBsb3RfdnRfYWRfNCA8LSBoZWF0bWFwX2Z1bihlZmFfdnRfYWRfNCkgKyAKICBndWlkZXMoZmlsbCA9ICJub25lIikgKyAKICBsYWJzKHggPSAiVmFudWF0dTogYWR1bHRzIikgKwogIHRoZW1lKGF4aXMudGl0bGUueCA9IGVsZW1lbnRfdGV4dChoanVzdCA9IDApKQoKcGxvdF92dF9jaF80IDwtIGhlYXRtYXBfZnVuKGVmYV92dF9jaF80KSArIAogIGd1aWRlcyhmaWxsID0gIm5vbmUiKSArIAogIGxhYnMoeCA9ICJWYW51YXR1OiBjaGlsZHJlbiIpICsKICB0aGVtZShheGlzLnRpdGxlLnggPSBlbGVtZW50X3RleHQoaGp1c3QgPSAwKSkKYGBgCgpgYGB7ciwgZmlnLmFzcCA9IDEuNX0KcGxvdF9ncmlkKCNwbG90X3VzX2FkXzQsIAogICAgICAgICAgcGxvdF9naF9hZF80LCBwbG90X2doX2NoXzQsIHBsb3RfdGhfYWRfNCwgCiAgICAgICAgICBwbG90X3RoX2NoXzQsIHBsb3RfdnRfYWRfNCwgcGxvdF92dF9jaF80LCAKICAgICAgICAgIG5jb2wgPSAyLCBsYWJlbHMgPSBjKCJBIiwgIkIiLCAiQyIsICJEIiwgIkUiLCAiRiIsICJHIikpCmBgYAoKIyBDb3VudHMKCmBgYHtyfQpwYXN0ZSgiVVMgYWR1bHRzOiIsIG5yb3coZF91c19hZF9waWxvdCkpCnBhc3RlKCJHSCBhZHVsdHM6IiwgbnJvdyhkX2doX2FkKSkKcGFzdGUoIkdIIGNoaWxkcmVuOiIsIG5yb3coZF9naF9jaCkpCnBhc3RlKCJUSCBhZHVsdHM6IiwgbnJvdyhkX3RoX2FkKSkKcGFzdGUoIlRIIGNoaWxkcmVuOiIsIG5yb3coZF90aF9jaCkpCnBhc3RlKCJWVCBhZHVsdHM6IiwgbnJvdyhkX3Z0X2FkKSkKcGFzdGUoIlZUIGNoaWxkcmVuOiIsIG5yb3coZF92dF9jaCkpCgpwYXN0ZSgiTm9uLVVTOiIsIHN1bShucm93KGRfZ2hfYWQpLCBucm93KGRfZ2hfY2gpLAogICAgICAgICAgICAgICAgICAgICBucm93KGRfdGhfYWQpLCBucm93KGRfdGhfY2gpLAogICAgICAgICAgICAgICAgICAgICBucm93KGRfdnRfYWQpLCBucm93KGRfdnRfY2gpKSkKYGBgCgo=